package net.j4love.concurrency.practice.c1;

import org.junit.Test;

import java.util.concurrent.CountDownLatch;

/**
 * @author he peng
 * @create 2018/6/25 13:39
 * @see
 */
public class SafeSequenceTest {

    class SafeSequence {
        private int value;

        public synchronized int next() {
            try {
                // 模拟放弃 cpu 执行权
                Thread.sleep(50);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            // ++ 不是一个原子操作
            return this.value++;
        }
    }

    class MyThread extends Thread {
        SafeSequenceTest.SafeSequence safeSequence;
        CountDownLatch countDownLatch;

        public MyThread(String name, SafeSequenceTest.SafeSequence safeSequence, CountDownLatch countDownLatch) {
            super(name);
            this.safeSequence = safeSequence;
            this.countDownLatch = countDownLatch;
        }

        @Override
        public void run() {
            for (int i = 0 ; i < 20 ; i++) {
                System.out.println(Thread.currentThread().getName() + " , next = " + safeSequence.next());
            }
            countDownLatch.countDown();
        }
    }

    @Test
    public void test1() throws Exception {
        CountDownLatch countDownLatch = new CountDownLatch(3);
        SafeSequenceTest.SafeSequence safeSequence = new SafeSequenceTest.SafeSequence();

        new SafeSequenceTest.MyThread("SafeSequenceTest-Thread-1" , safeSequence , countDownLatch).start();
        new SafeSequenceTest.MyThread("SafeSequenceTest-Thread-2" , safeSequence , countDownLatch).start();
        new SafeSequenceTest.MyThread("SafeSequenceTest-Thread-3" , safeSequence , countDownLatch).start();

        countDownLatch.await();

    }

}
